home *** CD-ROM | disk | FTP | other *** search
/ MacHack 1998 / MacHack 1998.toast / The Hacks! / Interim Executive Decision / Outline Table Demo / sources / CDirectoryItem.cp next >
Encoding:
Text File  |  1998-06-21  |  9.2 KB  |  376 lines  |  [TEXT/CWIE]

  1. //============================================================================
  2. // CDirectoryItem.cp        ©1997 Metrowerks Inc. All rights reserved
  3. // Original author: John C. Daub
  4. //============================================================================
  5. // A concrete LOutlineItem for items of type "directory".
  6.  
  7. #include "CDirectoryItem.h"
  8. #include "CFileItem.h"
  9. #include "SendFinderOpen.h"
  10. #include <LOutlineItem.h>
  11. #include <LOutlineTable.h>
  12. #include <UGAColorRamp.h>
  13.  
  14. #include <Gestalt.h>
  15.  
  16. #include "OutlineTablePrefix.h"
  17.  
  18. extern Handle gOnIcon;
  19. extern Handle gOffIcon;
  20.  
  21. #include "GetFileIcon.h"
  22.  
  23. /* !!!!!! Add new gestalt selector names here !!!!!! */
  24.  
  25. StringPtr gGestaltNames[] =
  26. {
  27.     "\pDrag Manager"
  28. };
  29.  
  30. CDirectoryItem::CDirectoryItem( int nameId, OSType selector, Uint32 subValues )
  31. {
  32.     // store the FSSpec for the file associated with this item.
  33.     
  34.     // Note that even tho we are storing data for an item within
  35.     // the outline item, this doesn't provide any sort of persistant
  36.     // storage of data within the table (see comments in COutlineTable's
  37.     // ctor about mTableStorage).
  38.     
  39.     // The reason for this is how the outline table class deals with
  40.     // expansion and collapsing of hierarchical nodes... when you expand
  41.     // the item's ExpandSelf method is called. And as things are expanded
  42.     // and such, items are created.. as collapsed, they are deleted. So
  43.     // there is no persistance of the outline items and their stored data.
  44.     
  45.     // This is also why you might have a deep expansion of nested hierarchies
  46.     // in the table, but you collapse a top-level parent, reexpand that and
  47.     // the expand/nesting hierarchy is not maintained... everything was
  48.     // deleted and has to be recreated.
  49.  
  50.     fSelector = selector;
  51.     fSubValues = subValues;
  52.     fNameId = nameId;
  53.     fState = false;
  54. }
  55.  
  56.  
  57. // dtor
  58.  
  59. CDirectoryItem::~CDirectoryItem()
  60. {
  61. }
  62.  
  63. // determine what it is that we're to draw in a given column
  64.  
  65. void
  66. CDirectoryItem::GetDrawContentsSelf(
  67.     const STableCell&        inCell,
  68.     SOutlineDrawContents&    ioDrawContents)
  69. {
  70.  
  71.     switch (inCell.col)
  72.     {
  73.         default:
  74.         {
  75.             ioDrawContents.outShowSelection = true;
  76.             ioDrawContents.outHasIcon = false; //true;
  77.             ioDrawContents.outIconSuite = nil; //(fState? gOnIcon : gOffIcon);
  78.             ioDrawContents.outTextTraits.style |= bold;
  79.             
  80.             if (fNameId >= 0)
  81.             {
  82.                 LString::CopyPStr(gGestaltNames[fNameId], ioDrawContents.outTextString);
  83.             }
  84.             else
  85.             {
  86.                 Str255            tmpName;
  87.                 LString::FourCharCodeToPStr(fSelector, tmpName);
  88.                 LString::CopyPStr(tmpName, ioDrawContents.outTextString);
  89.             }
  90.             
  91.             break;
  92.         }
  93. #if 000000
  94.         case 2:
  95.         {
  96.             ioDrawContents.outShowSelection = true;
  97.             ioDrawContents.outHasIcon = false;
  98.             ioDrawContents.outTextTraits.style = 0;
  99.             
  100.             LString::CopyPStr("\p-", ioDrawContents.outTextString);
  101.             
  102.             break;
  103.         }
  104. #endif
  105.     }
  106. }
  107.  
  108.  
  109. // by default, rows are not expanders.. but since this is a directory
  110. // and we're showing hierarchy, of course we need to be able to expand.
  111. // So we must make sure the table is aware of that fact.
  112.  
  113. Boolean
  114. CDirectoryItem::CanExpand() const
  115. {    
  116.     return true;
  117. }
  118.  
  119.  
  120. // just to be cute, draw an adornment of a gray background
  121.  
  122. void
  123. CDirectoryItem::DrawRowAdornments(
  124.     const Rect&        inLocalRowRect )
  125. {
  126.     ShadeRow(UGAColorRamp::GetColor(2), inLocalRowRect);
  127. }
  128.  
  129.  
  130. // this is the magic of what we do when someone tries to
  131. // expand this item. We create outline items for all possible subitems.
  132. // We do not need to destruct these (in CollapseSelf) as that is
  133. // handled for us automatically.. see comments in LOutlineItem.cp for
  134. // more information
  135.  
  136. void
  137. CDirectoryItem::ExpandSelf()
  138. {
  139.  
  140.     LOutlineItem*    theItem = nil;
  141.     LOutlineItem*    lastItem = nil;
  142.     UInt32            i;
  143.  
  144.     for (i = 0; i < 32; i++)
  145.     {
  146.         if (fSubValues & (1L << i))
  147.         {
  148.             // it's a gestalt item
  149.             
  150.             theItem = new CFileItem( -1, fSelector, i );
  151.             ThrowIfNil_(theItem);
  152.         
  153.             // and insert it at the end of the table
  154.         
  155.             mOutlineTable->InsertItem( theItem, this, lastItem );
  156.             lastItem = theItem;
  157.         }
  158.     }
  159.  
  160. #if 000000
  161.         /****** Duplicate a block like  */
  162.  
  163.         // it's a gestalt item
  164.             
  165.         theItem = new CFileItem( 0, gestaltDragMgrAttr, gestaltDragMgrPresent );
  166.         ThrowIfNil_(theItem);
  167.         
  168.         // and insert it at the end of the table
  169.         
  170.         mOutlineTable->InsertItem( theItem, this, lastItem );
  171.         lastItem = theItem;
  172.  
  173.         /****** this for an item */
  174.         
  175.         // it's a gestalt item
  176.             
  177.         theItem = new CFileItem( 1, gestaltDragMgrAttr, gestaltDragMgrFloatingWind );
  178.         ThrowIfNil_(theItem);
  179.         
  180.         // and insert it at the end of the table
  181.         
  182.         mOutlineTable->InsertItem( theItem, this, lastItem );
  183.         lastItem = theItem;
  184.         
  185.         // it's a gestalt item
  186.             
  187.         theItem = new CFileItem( 2, gestaltDragMgrAttr, gestaltPPCDragLibPresent );
  188.         ThrowIfNil_(theItem);
  189.         
  190.         // and insert it at the end of the table
  191.         
  192.         mOutlineTable->InsertItem( theItem, this, lastItem );
  193.         lastItem = theItem;
  194.         
  195.         // it's a gestalt item
  196.             
  197.         theItem = new CFileItem( 3, gestaltDragMgrAttr, gestaltDragMgrHasImageSupport );
  198.         ThrowIfNil_(theItem);
  199.         
  200.         // and insert it at the end of the table
  201.         
  202.         mOutlineTable->InsertItem( theItem, this, lastItem );
  203.         lastItem = theItem;
  204.         
  205.         // it's a gestalt item
  206.             
  207.         theItem = new CFileItem( 4, gestaltDragMgrAttr, gestaltCanStartDragInFloatWindow );
  208.         ThrowIfNil_(theItem);
  209.         
  210.         // and insert it at the end of the table
  211.         
  212.         mOutlineTable->InsertItem( theItem, this, lastItem );
  213.         lastItem = theItem;
  214.     }
  215. #endif
  216.  
  217. /* !!!!!! Add new gestalt items names here !!!!!! */
  218.  
  219. #if 000000
  220.  
  221.     CInfoPBRec folderInfo;
  222.     Str31 dirFileName;
  223.     LString::CopyPStr( mFileSpec.name, dirFileName, sizeof(Str31) );
  224.     
  225.     // find the info for this directory (mostly to get it's dirID)
  226.     folderInfo.hFileInfo.ioCompletion = nil;
  227.     folderInfo.hFileInfo.ioNamePtr = dirFileName;
  228.     folderInfo.hFileInfo.ioVRefNum = mFileSpec.vRefNum;
  229.     folderInfo.hFileInfo.ioFDirIndex = 0;
  230.     folderInfo.hFileInfo.ioDirID = mFileSpec.parID;
  231.  
  232.     ThrowIfOSErr_(::PBGetCatInfoSync( &folderInfo ));
  233.  
  234.     LOutlineItem *theItem = nil;
  235.     Int16 index = 1;
  236.     LOutlineItem *lastItem = nil;
  237.  
  238.     while ( true ) {
  239.     
  240.         // and recurse through this folder to list its contents
  241.         
  242.         CInfoPBRec fileInfo;
  243.         Str31 fileName;
  244.         
  245.         fileInfo.hFileInfo.ioCompletion = nil;
  246.         fileInfo.hFileInfo.ioNamePtr = fileName;
  247.         fileInfo.hFileInfo.ioVRefNum = folderInfo.hFileInfo.ioVRefNum;
  248.         fileInfo.hFileInfo.ioFDirIndex = index++;
  249.         fileInfo.hFileInfo.ioDirID = folderInfo.hFileInfo.ioDirID;
  250.     
  251.         OSErr err = ::PBGetCatInfoSync( &fileInfo );    
  252.         if ( err != noErr )
  253.             break;
  254.                 
  255.         // we ignore invis stuff
  256.         if ( fileInfo.hFileInfo.ioFlFndrInfo.fdFlags & kIsInvisible )
  257.             continue;
  258.  
  259.         // make an FSSpec for the file
  260.         
  261.         FSSpec theSpec;
  262.         
  263.         ThrowIfOSErr_(::FSMakeFSSpec( folderInfo.hFileInfo.ioVRefNum,
  264.                         folderInfo.hFileInfo.ioDirID,
  265.                         fileName,
  266.                         &theSpec ));
  267.         
  268.         // make an outline item based upon a directory or file
  269.         
  270.         if ( fileInfo.hFileInfo.ioFlAttrib & ioDirMask )
  271.         {
  272.             // it's a directory
  273.             
  274.             theItem = new CDirectoryItem( theSpec );
  275.             ThrowIfNil_(theItem);
  276.         }
  277.         else
  278.         {
  279.             // it's a file
  280.             
  281.             theItem = new CFileItem( theSpec );
  282.             ThrowIfNil_(theItem);
  283.         }
  284.         
  285.         // and insert it at the end
  286.         
  287.         mOutlineTable->InsertItem( theItem, this, lastItem );
  288.         lastItem = theItem;
  289.     }
  290. #endif
  291. }
  292.  
  293. // send an open document AppleEvent to the Finder to open this
  294. // given directory
  295.  
  296. void
  297. CDirectoryItem::DoubleClick(
  298.     const STableCell&            /* inCell */,
  299.     const SMouseDownEvent&        /* inMouseDown */,
  300.     const SOutlineDrawContents&    /* inDrawContents */,
  301.     Boolean                        /* inHitText */)
  302. {
  303. #if 000000
  304.     ThrowIfOSErr_(SendFinderOpenAE(&mFileSpec));
  305. #endif
  306. }
  307.  
  308. // ---------------------------------------------------------------------------
  309. //        * TrackContentClick                                        [protected]
  310. // ---------------------------------------------------------------------------
  311. //    Called by ClickCell whenever a mouse-down event occurs within
  312. //    the contents (icon or text) of this cell. Selects or deselects this
  313. //    cell as appropriate and tests for dragging or double-clicking.
  314.  
  315. void
  316. CDirectoryItem::TrackContentClick(
  317.     const STableCell&            /*inCell*/,
  318.     const SMouseDownEvent&        inMouseDown,
  319.     const SOutlineDrawContents&    /*inDrawContents*/,
  320.     Boolean                        /*inHitText*/)
  321. {
  322. #if 000000
  323.     // If item isn't selected, try to select it now.
  324.     
  325.     Boolean wasSelected = mOutlineTable->CellIsSelected(inCell);
  326.     if (!wasSelected) {
  327.         if (!(inMouseDown.macEvent.modifiers & shiftKey))
  328.             mOutlineTable->UnselectAllCells();
  329.         mOutlineTable->SelectCell(inCell);
  330.         mOutlineTable->UpdatePort();
  331.     }
  332. #endif    
  333.     // See if mouse moves. If it does, track a drag from it
  334.     
  335.     if (::StillDown() && ::WaitMouseMoved(inMouseDown.macEvent.where)) {
  336. //        TrackDrag(inCell, inMouseDown, inDrawContents);
  337.         return;
  338.     }
  339.  
  340. #if 000000
  341.     // Mouse didn't move, see if this was a double-click.
  342.     
  343.     if (LPane::GetClickCount() > 1) {
  344.         DoubleClick(inCell, inMouseDown, inDrawContents, inHitText);
  345.         return;
  346.     }
  347.  
  348.     // If none of the above, and shift key was down, deselect this cell.
  349.     
  350.     if (wasSelected && (inMouseDown.macEvent.modifiers & shiftKey)) {
  351.         mOutlineTable->UnselectCell(inCell);
  352.         mOutlineTable->UpdatePort();
  353.         return;
  354.     }
  355.  
  356.     // Simple click and item is still selected, call it a single click.
  357.  
  358.     if (mOutlineTable->CellIsSelected(inCell)) {
  359.         SingleClick(inCell, inMouseDown, inDrawContents, inHitText);
  360.         return;
  361.     }
  362. #endif
  363.     
  364.     SetState((fState ? false : true));
  365.     return;    
  366. }
  367.  
  368. void CDirectoryItem::SetState(bool state)
  369. {
  370.     fState = state;
  371.     mOutlineTable->Refresh();
  372.  
  373. /* !!!!!! Handle group selection/deselection here !!!!!! */
  374.  
  375.     return;
  376. }